package com.clp.protocol.iec104.definition;

import com.clp.protocol.core.utils.EnumElemDoesNotExistException;
import lombok.AllArgsConstructor;
import lombok.Getter;

/**
 * 遥信的相关定义
 */
public interface Ts {
    @Getter
    @AllArgsConstructor
    enum VaryType {
        ONE_POINT(1, "单点遥信", TypeTag.M_SP_NA_1),
        TWO_POINT(2, "双点遥信", TypeTag.M_DP_NA_1);

        private final int val;
        private final String desc;
        private final TypeTag typeTag;
    }

    /**
     * 单点和双点遥信的 有效/无效位 的定义
     */
    @Getter
    @AllArgsConstructor
    enum Valid {
        /**
         * 0为有效
         */
        VALID(0, "有效"),
        /**
         * 1为无效
         */
        NOT_VALID(1, "无效");

        private final int value;
        private final String desc;

        /**
         * 根据值返回对应的状态
         */
        public static Valid gain(int value) {
            for (Valid valid : Valid.values()) {
                if (valid.getValue() == value) {
                    return valid;
                }
            }
            throw new EnumElemDoesNotExistException(Valid.class);
        }

        public static Valid gain(boolean isValid) {
            if (isValid) return VALID;
            return NOT_VALID;
        }
    }

    /**
     * 单点和双点遥信的 当前值/非当前值 的定义
     */
    @Getter
    @AllArgsConstructor
    enum CurrVal {
        /**
         * 0为当前值
         */
        CURR_VAL(0, "当前值"),
        /**
         * 1为非当前值
         */
        NOT_CURR_VAL(1, "非当前值");

        private final int value;
        private final String desc;

        public static CurrVal gain(int value) {
            for (CurrVal currVal : CurrVal.values()) {
                if (currVal.getValue() == value) {
                    return currVal;
                }
            }
            throw new EnumElemDoesNotExistException(CurrVal.class);
        }

        public static CurrVal gain(boolean isCurrVal) {
            if (isCurrVal) return CURR_VAL;
            return NOT_CURR_VAL;
        }
    }

    /**
     * 单点/双点遥信的 被取代/未被取代 的定义
     */
    @Getter
    @AllArgsConstructor
    enum Replace {
        /**
         * 1为被取代
         */
        REPLACE(1, "被取代"),
        /**
         * 0为未被取代
         */
        NOT_REPLACE(0, "未被取代");

        private final int value;
        private final String desc;

        public static Replace gain(int value) {
            for (Replace replace : Replace.values()) {
                if (replace.getValue() == value) {
                    return replace;
                }
            }
            throw new EnumElemDoesNotExistException(Replace.class);
        }

        public static Replace gain(boolean isReplaced) {
            if (isReplaced) return REPLACE;
            return NOT_REPLACE;
        }
    }

    /**
     * 单点/双点遥信的 被闭锁/未被闭锁 的定义
     */
    @Getter
    @AllArgsConstructor
    enum Lock {
        /**
         * 1为被闭锁
         */
        LOCK(1, "被闭锁"),
        /**
         * 0为未被闭锁
         */
        NOT_LOCK(0, "未被闭锁");

        private final int value;
        private final String desc;

        public static Lock gain(int value) {
            for (Lock lock : Lock.values()) {
                if (lock.getValue() == value) {
                    return lock;
                }
            }
            throw new EnumElemDoesNotExistException(Lock.class);
        }

        public static Lock gain(boolean isLocked) {
            if (isLocked) return LOCK;
            return NOT_LOCK;
        }
    }

    /**
     * 单点信息 开关状态 的定义
     */
    @Getter
    @AllArgsConstructor
    enum OnePointSwitch {
        /**
         * 1为开关合
         */
        SWITCH_ON(1, "开关合"),
        /**
         * 0为开关分
         */
        SWITCH_OFF(0, "开关分");

        private final int value;
        private final String desc;

        /**
         * 根据值返回对应的类型
         *
         * @param value
         */
        public static OnePointSwitch gain(int value) {
            for (OnePointSwitch onePointSwitch : OnePointSwitch.values()) {
                if (onePointSwitch.value == value) {
                    return onePointSwitch;
                }
            }
            throw new EnumElemDoesNotExistException(OnePointSwitch.class);
        }

        public static OnePointSwitch gain(boolean isSwitchOn) {
            if (isSwitchOn) return SWITCH_ON;
            return SWITCH_OFF;
        }
    }

    /**
     * 双点信息 开关状态 的定义
     */
    @Getter
    @AllArgsConstructor
    enum TwoPointSwitch {
        /**
         * 不确定或中间状态
         */
        UNSURE_OR_MIDDLE(0, "不确定或中间状态"),
        /**
         * 开关分
         */
        SWITCH_OFF(1, "开关分"),
        /**
         * 开关合
         */
        SWITCH_ON(2, "开关合"),
        /**
         * 不确定
         */
        UNSURE(3, "不确定");

        private int value;
        private String desc;

        /**
         * 根据值返回对应的类型
         *
         * @param value
         */
        public static TwoPointSwitch gain(int value) {
            for (TwoPointSwitch twoPointSwitch : TwoPointSwitch.values()) {
                if (twoPointSwitch.value == value) {
                    return twoPointSwitch;
                }
            }
            throw new EnumElemDoesNotExistException(TwoPointSwitch.class);
        }

        public static TwoPointSwitch gain(boolean isSwitchOn) {
            if (isSwitchOn) return SWITCH_ON;
            return SWITCH_OFF;
        }
    }
}
